package com.jiangxjsy.gateway.service.database.impl;

import com.alibaba.fastjson.JSON;
import com.jiangxjsy.core.constant.GatewayConstant;
import com.jiangxjsy.gateway.mapper.GatewayRouteMapper;
import com.jiangxjsy.gateway.service.database.GatewayRouteService;
import com.jiangxjsy.model.gateway.entity.GatewayRoute;
import lombok.extern.slf4j.Slf4j;
import org.springframework.cloud.gateway.filter.FilterDefinition;
import org.springframework.cloud.gateway.handler.predicate.PredicateDefinition;
import org.springframework.cloud.gateway.route.RouteDefinition;
import org.springframework.stereotype.Service;

import javax.annotation.PostConstruct;
import javax.annotation.Resource;
import java.net.URI;
import java.util.Collection;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.concurrent.ConcurrentHashMap;

/**
 * wukong-crm-master
 * 蒋胜宇
 * 2025/5/28 17:12
 */

@Service
@Slf4j
public class GatewayRouteServiceImpl implements GatewayRouteService {
    @Resource
    private GatewayRouteMapper gatewayRouteMapper;

    private final Map<String, RouteDefinition> ROUTES = new ConcurrentHashMap<>();

    /**
     * 删除路由
     *
     * @param routeId 路由ID
     */
    @Override
    public void removeRoute(String routeId) {
        ROUTES.remove(routeId);
    }

    /**
     * 保存路由
     *
     * @param routeDefinition 路由定义
     */
    @Override
    public void saveRoute(RouteDefinition routeDefinition) {
        ROUTES.put(routeDefinition.getId(), routeDefinition);
    }

    /**
     * 获取所有路由定义
     *
     * @return 路由定义集合
     */
    @Override
    public Collection<RouteDefinition> getRouteDefinitions() {
        return ROUTES.values();
    }

    /**
     * 从数据库中加载路由配置，Bean初始化时自动执行一次
     */
    @Override
    @PostConstruct
    public void loadRoute() {
        List<GatewayRoute> gatewayRoutes = gatewayRouteMapper.selectAll();
        for (GatewayRoute gatewayRoute : gatewayRoutes) {
            log.debug("Loading route with ID: {}, URI: {}, Predicates: {}, Filters: {}",
                    gatewayRoute.getId(),
                    gatewayRoute.getUri(),
                    gatewayRoute.getPredicates(),
                    gatewayRoute.getFilters()
            );

            RouteDefinition routeDefinition = new RouteDefinition();
            routeDefinition.setId(gatewayRoute.getRouteId());
            routeDefinition.setOrder(Math.toIntExact(gatewayRoute.getOrders()));
            routeDefinition.setUri(URI.create(gatewayRoute.getUri()));
            routeDefinition.setFilters(JSON.parseArray(gatewayRoute.getFilters(), FilterDefinition.class));
            routeDefinition.setPredicates(JSON.parseArray(gatewayRoute.getPredicates(), PredicateDefinition.class));
            Map<String, Object> metadata = new HashMap<>();
            metadata.put(GatewayConstant.ROUTER_INTERCEPT, gatewayRoute.getIntercept());
            metadata.put(GatewayConstant.ROUTER_DESCRIPTION, gatewayRoute.getDescription());
            routeDefinition.setMetadata(metadata);

            ROUTES.put(routeDefinition.getId(), routeDefinition);
        }
    }
}
